home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Tech Arsenal 1
/
Tech Arsenal (Arsenal Computer).ISO
/
tek-01
/
ldb.zip
/
BINDER.HPP
< prev
next >
Wrap
C/C++ Source or Header
|
1991-10-18
|
8KB
|
269 lines
/*
binder.hpp
10-18-91
Loose Data Binder v 1.4
Copyright 1991
John W. Small
All rights reserved
PSW / Power SoftWare
P.O. Box 10072
McLean, Virginia 22102 8072 USA
John Small
Voice: (703) 759-3838
CIS: 73757,2233
*/
#ifndef BINDER_HPP
#define BINDER_HPP
#include <limits.h> // UINT_MAX
/*
The "Loose Data Binder", or Binder for short, binds
any type of data together in a hybrid stack-queue-
deque-list-array structure. Like a loose leaf
notebook where you can insert or arrange leafs in
any fashion, the "Loose Data Binder" allows you to
collect and arrange data in any fashion. Think of
the Binder as an elastic array of void pointers.
The Binder is the equivalent of an extensive
container class hierarchy but without the confusing
complexity of a towering hierarchy.
*/
/* Various pointers and their NULLs */
typedef void * voiD;
#define voiD0 ((voiD)0)
typedef voiD * voiDV;
#define voiDV0 ((voiDV)0)
enum BDR_DEFAULTS {
BDR_MAXNODES = (UINT_MAX/sizeof(voiD)),
BDR_LIMIT = 20,
BDR_DELTA = 10,
BDR_NOTFOUND = BDR_MAXNODES
};
enum BDR_FLAG_BITS {
BDR_SORTED = 0x01,
BDR_OK_FREE = 0x02,
BDR_NO_FREE = 0x00
};
/* Search/sort compare function pointer type: */
typedef int (*BDRcomparE)(const voiD D1, const voiD D2);
#define BDRcomparE0 ((BDRcomparE)0)
/* Function pointer types for the Binder iterators: */
typedef void (*BDRforEachBlocK)
(voiD D, voiD M, voiD A);
typedef int (*BDRdetectBlocK)
(voiD D, voiD M);
class Binder;
typedef Binder * BindeR;
typedef void (*BDRcollectBlocK)
(voiD D, BindeR R, voiD M, voiD A);
/*
Gimmick for constructing without initializing:
to be used for loading instances from a stream
(see sbinder.hpp).
*/
typedef BindeR * UniqueBinderConST;
#define OnlyInitBinderVFT ((UniqueBinderConST)0)
/*
Gaurrantees Dfree() is only invoked when
(flags & BDR_OK_FREE) != 0.
*/
#define DFREE(Dexp) ((flags & BDR_OK_FREE)? Dfree(Dexp): 0)
class Binder {
protected:
unsigned lowLimit, lowThreshold, first;
voiDV linkS;
unsigned limit, delta, nodes, maxNodes;
unsigned curNode, flags;
BDRcomparE comparE;
void construct(unsigned flags, unsigned maxNodes,
unsigned limit, unsigned delta);
virtual int Dfree(voiD D)
/*
Dfree() is called by any Binder
primitive that attempts to delete
the data, D, it is unbinding, e.g.
atFree(), popFree(), etc. The
Binder must be constructed with
BDR_OK_FREE for Dfree() to be
called. In other words it is
guaranteed that Dfree() is never
called when BDR_OK_FREE is absent.
If D is NULL then zero must be
returned otherwise a nonzero value
must be returned regardless of
whether or not an overriding
function is successful in deleting
its data. Override this function to
implement calling your own node
destructors.
*/
{ return (D? delete D, 1 : 0); }
virtual int Dattach(voiD)
/*
Dattach() is called by any Binder
primitive that attempts to bind
data, e.g. atIns(), push(), etc.
This allows the data to become aware
of the binding process by overriding
Dattach(). The voiD parameter is a
pointer to the data about to be
bound and guaranteed never to be
NULL! If and only if the data can't
attach itself to the Binder, as
defined by the overriding function,
should zero be returned. Any
overriding function should only
"link" itself to the Binder but
should not use the implicit "this"
pointer to access Binder within the
overriding function. This
restriction applies because Binder
data may be in a transition state
when Dattach() is called. It is
however permissible to store the
"this" pointer within the data being
bound for later use in accessing
Binder data.
*/
{ return 1; }
virtual void Ddetach(voiD)
/*
Ddetach() is called by any Binder
primitive that attempts to unbind
data, e.g. atDel(), pop(), etc.
The voiD parameter is never NULL!
Once called, the data must consider
itself detached from the Binder!
*/
{ return; }
public:
Binder(UniqueBinderConST) {}
Binder(unsigned flags = BDR_NO_FREE,
unsigned maxNodes = BDR_MAXNODES,
unsigned limit = BDR_LIMIT,
unsigned delta = BDR_DELTA)
{ construct(flags,maxNodes,limit,delta); }
Binder(voiDV argv, int argc = 0,
unsigned flags = BDR_NO_FREE);
voiDV vector();
virtual ~Binder();
unsigned Limit() { return limit; }
unsigned setLimit(unsigned newLimit);
unsigned pack() { return setLimit(nodes); }
unsigned Delta() { return delta; }
unsigned setDelta(unsigned newDelta = BDR_DELTA);
unsigned Nodes() { return nodes; }
unsigned MaxNodes() { return maxNodes; }
unsigned setMaxNodes(unsigned newMaxNodes
= BDR_MAXNODES);
unsigned vacancy() { return maxNodes - nodes; }
unsigned vacancyNonElastic()
{ return limit - nodes; }
voiD atIns(unsigned n, const voiD D);
voiD atDel(unsigned n);
int allDel();
int atFree(unsigned n) { return DFREE(atDel(n)); }
int allFree();
voiD atPut(unsigned n, const voiD D);
voiD atGet(unsigned n);
voiD operator[](unsigned n) { return atGet(n); }
voiD atXchg(unsigned n, const voiD D);
unsigned index(const voiD D);
voiD add(const voiD D) { return atIns(nodes,D); }
Binder& operator+=(const voiD D)
{ atIns(nodes,D); return *this; }
voiD subtract(const voiD D)
{ return atDel(index(D)); }
Binder& operator-=(const voiD D)
{ atDel(index(D)); return *this; }
int forEach(BDRforEachBlocK B, voiD M = voiD0,
voiD A = voiD0);
unsigned firstThat(BDRdetectBlocK B, voiD M = voiD0);
unsigned lastThat(BDRdetectBlocK B, voiD M = voiD0);
int collect(BDRcollectBlocK B, BindeR R,
voiD M = voiD0, voiD A = voiD0);
/* FlexList like primitives: */
voiD top() { return atGet(0); }
voiD current() { return atGet(curNode); }
operator voiD() { return atGet(curNode); }
/*
The implicit (voiD) cast is meant to be
used in conjunction with the iterators and
not the << and >> operators!
*/
voiD bottom() { return atGet(nodes-1); }
unsigned CurNode();
int setCurNode(unsigned n = BDR_MAXNODES);
int Sorted() { return (flags & BDR_SORTED); }
void unSort() { flags &= ~BDR_SORTED; }
BDRcomparE ComparE() { return comparE; }
void setComparE(BDRcomparE comparE)
{ this->comparE = comparE;
flags &= ~BDR_SORTED; }
voiD push(const voiD D) { return atIns(0,D); }
voiD pop() { return atDel(0); }
int popFree() { return DFREE(atDel(0)); }
Binder& operator>>(voiD& D)
{ D = atDel(0); return *this; }
voiD insQ(const voiD D)
{ return atIns(nodes,D); }
Binder& operator<<(const voiD D)
{ atIns(nodes,D); return *this; }
Binder& operator<<(Binder& (*manipulator)
(Binder& B));
voiD rmQ() { return atDel(0); }
int rmQFree() { return DFREE(atDel(0)); }
voiD unQ() /* Remove from rear of Q */
{ return atDel(nodes-1); }
int unQFree() { return DFREE(atDel(nodes-1)); }
voiD ins(const voiD D);
voiD insSort(const voiD D);
voiD del();
int delFree() { return DFREE(del()); }
voiD next();
voiD operator++() { return next(); }
voiD prev();
voiD operator--() { return prev(); }
voiD findFirst(const voiD K);
voiD findNext(const voiD K);
voiD findLast(const voiD K);
voiD findPrev(const voiD K);
int sort(BDRcomparE comparE = BDRcomparE0);
};
#endif